package com.rivues.util.tools;

import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.math.BigDecimal;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;

import javax.servlet.http.HttpServletRequest;

import mondrian.olap.LevelType;

import org.apache.commons.beanutils.BeanUtils;
import org.apache.commons.lang.StringUtils;
import org.codehaus.jackson.annotate.JsonAnyGetter;
import org.hibernate.criterion.DetachedCriteria;
import org.hibernate.criterion.Order;
import org.hibernate.criterion.Restrictions;

import com.googlecode.aviator.AviatorEvaluator;
import com.rivues.core.RivuDataContext;
import com.rivues.module.platform.web.model.AnalyzerReport;
import com.rivues.module.platform.web.model.AnalyzerReportModel;
import com.rivues.module.platform.web.model.Cube;
import com.rivues.module.platform.web.model.CubeLevel;
import com.rivues.module.platform.web.model.CubeMeasure;
import com.rivues.module.platform.web.model.Dimension;
import com.rivues.module.platform.web.model.DrillDown;
import com.rivues.module.platform.web.model.MeasureGroup;
import com.rivues.module.platform.web.model.MeasureGroupData;
import com.rivues.module.platform.web.model.RenameCol;
import com.rivues.module.platform.web.model.ReportCellMerge;
import com.rivues.module.platform.web.model.ReportCol;
import com.rivues.module.platform.web.model.ReportFilter;
import com.rivues.module.platform.web.model.User;
import com.rivues.module.platform.web.model.Warning;
import com.rivues.module.report.web.model.PublishedReport;
import com.rivues.util.RivuTools;
import com.rivues.util.data.FirstTitle;
import com.rivues.util.data.Level;
import com.rivues.util.data.ReportData;
import com.rivues.util.data.ValueData;
import com.rivues.util.iface.report.ReportFactory;
import com.rivues.util.serialize.JSON;

import freemarker.template.TemplateException;

public class RivuReportDataUtil {
	
	/**
	 * 填充维度标题
	 * @param model
	 * @param reportData
	 */
	public static void processFullFirstTitle(AnalyzerReportModel model , ReportData reportData){
		if(reportData.getRow()==null||reportData.getRow().getFirstTitle()!=null||StringUtils.isBlank(model.getRowdimension()))return;
		
		List<FirstTitle> firstTitles = new ArrayList<FirstTitle>();
		FirstTitle firstTitle = null;
		String[] levelids = model.getRowdimension().split(",");
		List<CubeLevel> levels = RivuDataContext.getService().findAllByCriteria(DetachedCriteria.forClass(CubeLevel.class)
				.add(Restrictions.eq("orgi", model.getOrgi())).addOrder(Order.asc("sortindex")));
		List<CubeLevel> cubeLevels = new ArrayList<CubeLevel>();
		for (String levelid : levelids) {
			cubeLevels.addAll(getLevels(levels, levelid));
		}
		List<CubeLevel> distinct_lls = new ArrayList<CubeLevel>();
		for (CubeLevel cubeLevel : cubeLevels) {
			if(!checkLevelIsExist(distinct_lls, cubeLevel.getId())){
				distinct_lls.add(cubeLevel);
			}
		}
		for (CubeLevel cubeLevel : distinct_lls) {
			firstTitle = new FirstTitle();
			firstTitle.setDepth(0);
			firstTitle.setName(cubeLevel.getName());
			firstTitles.add(firstTitle);
		}
		
		
		reportData.getRow().setFirstTitle(firstTitles);
		
	}
	
	private static boolean checkLevelIsExist(List<CubeLevel> levels,String levelid){
		boolean flag = false;
		for (CubeLevel cubeLevel : levels) {
			if(cubeLevel.getId().equals(levelid)){
				flag = true;
				break;
			}
		}
		
		return flag;
	}
	
	/**
	 * 根据需要获取指定的维度成员
	 * @param levels
	 * @param levelid
	 * @return
	 */
	private static List<CubeLevel> getLevels(List<CubeLevel> levels,String levelid){
		List<CubeLevel> lls = new ArrayList<CubeLevel>();
		CubeLevel curLevel = null;
		for (CubeLevel cubeLevel : levels) {
			if(cubeLevel.getId().equals(levelid)){
				curLevel = cubeLevel;
				break;
			}
		}
		if(curLevel!=null){
			for (CubeLevel cubeLevel : levels) {
				if(cubeLevel.getDimid().equals(curLevel.getDimid())&&cubeLevel.getSortindex()>=curLevel.getSortindex()){
					lls.add(cubeLevel);
				}
			}
		}
		return lls;
	}

	/**
	 * 隐藏所选列
	 * @param model
	 * @param reportData
	 */
	public static void processHiddencol(AnalyzerReportModel model , ReportData reportData){
		if(StringUtils.isBlank(model.getHiddencolstr())||reportData==null) return;//如果没有的话不进行设置，返回
		
		if(reportData.getCol()!=null && reportData.getCol().getTitle()!=null&&reportData.getCol().getTitle().get(0)!=null){
			String[] hiddencols = JSON.parseObject(model.getHiddencolstr(), String[].class);
			if(hiddencols==null)return;
			for (String str : hiddencols) {
				
				for (int j = 0; j < reportData.getCol().getTitle().get(0).size(); j++) {
					if(reportData.getCol().getTitle().get(0).get(j).getName().equals(str)){
						reportData.getCol().getTitle().get(0).remove(j);
						j--;
					}
				}
				for (List<ValueData> datas :reportData.getData()) {
					for (int i = 0; i < datas.size(); i++) {
						if(datas.get(i).getName().equals(str)){
							datas.remove(i);
							i--;
						}
					}
				}
			}
		}
		
		
	}
	
	
	/**
	 * q清理reportdata的表头信息
	 * @param model
	 * @param reportData
	 */
	public static void cleanTitle(AnalyzerReportModel model , ReportData reportData){
		if(reportData!=null){
			if(reportData.getRow()!=null && reportData.getRow().getFirstTitle()!=null){
				for(FirstTitle firstTitle : reportData.getRow().getFirstTitle()){
					firstTitle.setRename(null) ;
				}
				if(reportData.getCol()!=null && reportData.getCol().getTitle()!=null){
					for(List<Level> levelList : reportData.getCol().getTitle()){
						for(Level level : levelList){
							level.setRename(null) ;	//清除重命名
						}
					}
				}
			}
		}
		
	}
	
	/**
	 * 清理 data
	 * @param model
	 * @param reportData
	 */
	public static void clearReportData(AnalyzerReportModel model , ReportData reportData){
		for(int i=0 ; i<reportData.getCol().getTitle().get(0).size() ;){
			Level level = reportData.getCol().getTitle().get(0).get(i) ;
			if("newcol".equals(level.getLeveltype())){
				reportData.getCol().getTitle().get(0).remove(i)  ;
			}else{
				 i++ ;
			}
		}
		for(int row = 0 ; row < reportData.getData().size() ; row++){
			for(int col = 0 ; col < reportData.getData().get(row).size() ; col++){
				ValueData valueData = reportData.getData().get(row).get(col) ;
				if("newcol".equals(valueData.getValueType())){
					reportData.getData().get(row).remove(valueData) ;
					col--;
				}else{
					if(valueData.getCellmergeid()!=null){
						String formatStr = valueData.getFormatStr() ;
						if(formatStr!=null){
							java.text.NumberFormat numberFormat = new DecimalFormat(formatStr);
							if(valueData.getValue()!=null && valueData.getValue() instanceof Number){
								valueData.setForamatValue(numberFormat.format(((Number)valueData.getValue()).doubleValue())) ;
							}else{
								valueData.setForamatValue("") ;
							}
						}else{
							valueData.setForamatValue(String.valueOf(valueData.getValue())) ;
						}
					}
					valueData.setCellmergeid(null) ; 
					valueData.setRowspan(0) ;
					valueData.setColspan(0) ;
					valueData.setMerge(false) ;
				}
			}
		}
	}
	
	/**
	 * 以下代码功能修改，变成合并单元格  
	 * @param model
	 * @param reportData
	 */
	public static void processCellMerge(AnalyzerReportModel model , ReportData reportData){
		if(model.getRowformatstr()!=null && model.getRowformatstr().length()>0){
			List<Object> rowFormatList = JSON.parseObject(model.getRowformatstr(), List.class) ;
			for(int i=0 ; rowFormatList!=null && rowFormatList.size() >0 && i<rowFormatList.size() ; i++){
				boolean hasMerged = false ;
				String type = "";
				try {
					type = BeanUtils.getProperty(rowFormatList.get(i), "type");
				} catch (IllegalAccessException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				} catch (InvocationTargetException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				} catch (NoSuchMethodException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
				/**  以下处理单元格合并  **/
				if(type!=null && type.equals("cellmerge")){
					ReportCellMerge merge = (ReportCellMerge) rowFormatList.get(i) ;
					if(merge.getStartRow()>= 0 && merge.getStartCol() >= 0 && merge.getStartRow() < reportData.getData().size() && merge.getEndRow() < reportData.getData().size() && merge.getStartCol() <reportData.getData().get(merge.getStartRow()).size() && merge.getEndCol()< reportData.getData().get(merge.getStartRow()).size()){
						ValueData valueData = reportData.getData().get(merge.getStartRow()).get(merge.getStartCol()) ;
						/**
						 * 以下代码先找到合并单元格范围内是否已有 合并
						 */
						for(int row = merge.getStartRow() ; row<= merge.getEndRow() && row<reportData.getData().size()  ; row++){
							for(int col = merge.getStartCol() ; col <= merge.getEndCol() && col <reportData.getData().get(row).size() ; col++){
								ValueData mergeData = reportData.getData().get(row).get(col) ;
								if(mergeData.isMerge() || mergeData.getCellmergeid()!=null){
									hasMerged = true ;
									break ;
								}
							}
							if(hasMerged){
								break ;
							}
						}
						if(!hasMerged){
							int avgNum = 0 , avgNumExp = 0 ;
							valueData.setCellmergeid(merge.getId()) ;
							valueData.setColspan(merge.getEndCol() - merge.getStartCol()+1) ;
							valueData.setRowspan(merge.getEndRow() - merge.getStartRow()+1) ;
							Object mergeValue = valueData.getValue() ;
							for(int row = merge.getStartRow() ; row<= merge.getEndRow() ; row++){
								for(int col = merge.getStartCol() ; col <= merge.getEndCol() ; col++){
									ValueData mergeData = reportData.getData().get(row).get(col) ;
									if(mergeData!=null && mergeData.getValue()!=null && mergeData.getValue() instanceof Number && ((Number)mergeData.getValue()).intValue()!=0){
										avgNumExp++;
									}
									avgNum++ ;
									if(avgNum==1){
										continue ;
									}
									mergeData.setMerge(true) ;
									mergeValue = mergeValue(mergeValue , mergeData , merge.getMergetype());
									
									/**
									 * 
									 * mergeData.setMergevalue(valueData); 必须位于最后一行，否则 合并单元格会有问题
									 */
									mergeData.setMergevalue(valueData);
								}
							}
							aggValueData(merge.getMergetype() , "avgexp".equals(merge.getMergetype())? avgNumExp : avgNum , mergeValue , valueData , merge.getFormat()) ;
						}
					}
				}
			}
		}
		
	}
	
	/**
	 * 以下代码功能修改，变成增加行列
	 * @param model
	 * @param reportData
	 */
	public static void processNewCol(AnalyzerReportModel model , ReportData reportData , List<Object> colList) throws Exception{
		
		for(Object data : colList){
			String celltype = BeanUtils.getProperty(data, "type") ;
			if(celltype!=null && celltype.equals("colrow")){
				ReportCol reportCol = (ReportCol)data ;
				if(reportCol.isPosdef()){
					/**
					 * 选择的自定义列位置是指标
					 */
					for(FirstTitle firstTitle : reportData.getCol().getFirstTitle()){
						if(firstTitle.getName().equals(reportCol.getColpos())){
							List<Level> titleList = reportData.getCol().getTitle().get(reportData.getCol().getFirstTitle().indexOf(firstTitle)) ;
							int colindex = 0 , groupstart = 0 , curparentcolspan = 0 ;
							for(int i = 0 ; i< titleList.size() ; i++ ){
								Level level = titleList.get(i) ;
								/**
								 * 
								 */
								groupstart = groupstart + level.getColspan() ;
								curparentcolspan = level.getColspan();
								colindex = colindex + level.getColspan() ;
								
								
								if(level.getName().equals(reportCol.getColpositem())){
									int index = titleList.indexOf(level)+1 ;
									/**
									 * 如果是插入列类型是 CUR，则遍历所有最后一层级，然后为每个符合条件的指标添加汇总
									 */
									if(RivuDataContext.ReportNewColType.CUR.toString().equals(reportCol.getColpostype()) || RivuDataContext.CUBE_TITLE_MEASURE.equals(reportCol.getColpos())){
										Level tempLevel = level;
										while((tempLevel = tempLevel.getParent())!=null){
											tempLevel.setColspan(tempLevel.getColspan()+1) ;
										}
										
										processNewColWithIndex(reportData, reportCol, groupstart , groupstart - curparentcolspan , groupstart) ;
										titleList.add(index , new Level(reportCol.getName() , reportCol.getId(), "newcol", reportData.getCol().getTitle().size() , 1 , null , false , false)) ;
										groupstart = groupstart + 1;
										curparentcolspan = curparentcolspan + 1 ;
									}else{
										/**
										 * 如果插入列类型选择的是 NEXT，则需要为下一级的每一个选项添加 列
										 */
										groupstart = groupstart - curparentcolspan ;
										
										for(Level childLevel : level.getChilderen()){
//											curparentcolspan = childLevel.getColspan() ;
											Level tempLevel = childLevel;
											while((tempLevel = tempLevel.getParent())!=null){
												tempLevel.setColspan(tempLevel.getColspan()+1) ;
											}
//											childLevel.setColspan(childLevel.getColspan()+1) ;
											groupstart = groupstart + childLevel.getColspan() ;
											/**
											 * 找到TitleList
											 */
											List<Level> curTitleList = reportData.getCol().getTitle().get(reportData.getCol().getFirstTitle().indexOf(firstTitle)+1) ;
											for(Level tl : curTitleList){
												if(tl.getCubeLevel(tl.getDimname()).equals(childLevel.getCubeLevel(childLevel.getDimname())) && tl.getName().equals(childLevel.getName())){
													curTitleList.add(curTitleList.indexOf(tl)+1 , new Level(reportCol.getName() , reportCol.getId(), "newcol", reportData.getCol().getTitle().size() , 1 , null , false , false)) ;
													processNewColWithIndex(reportData, reportCol, groupstart  , colindex , groupstart + curparentcolspan) ;
													groupstart = groupstart + 1;
													break ;
												}
											}
										}
									}
									groupstart = groupstart + curparentcolspan ;
									i++;
								}
							}
							break ;
						}
					}
				}else{
					int index = reportData.getCol().getTitle().size()-1 ;
					processNewColWithIndex(reportData, reportCol, reportData.getCol().getTitle().get(index).size() , 0 ,reportData.getData().get(0).size()) ;
					Level level = new Level(reportCol.getName() , reportCol.getId(), "newcol", reportData.getCol().getTitle().size() , 1 , null , false , false) ;
					reportData.getCol().getTitle().get(0).add(level) ;
				}
			}
		}
		
		
	}
	
	public static void processNewColWithIndex(ReportData reportData  , ReportCol reportCol , int index , int start , int end){
		/**  以下处理新增单元格合并  **/
		
		for(int rowinx = 0  ; rowinx<reportData.getData().size() ; rowinx++){
			ValueData newColValueData = null ;
			if(reportCol.getExpress()!=null && reportCol.getExpress().trim().length()>0){
				Object value = null ;
				if(!reportCol.getExpress().equalsIgnoreCase("ALL")){
					Map<String, Object> context = new HashMap<String , Object>();
					List<Level> title = reportData.getCol().getTitle().get(reportData.getCol().getTitle().size()-1);
					for(int colinx = reportCol.isColgroup() ? start : 0 ; rowinx <reportData.getData().size() && colinx <( reportCol.isColgroup() ? end :reportData.getData().get(rowinx).size() ); colinx++){
						ValueData valueData = reportData.getData().get(rowinx).get(colinx) ;
						String no = RivuTools.getInx2Char(colinx) ;
						/**
						 * JEXL 2 不支持中文标签名称
						 */
						//							context.set(valueData.getName(), valueData.getValue()!= null ? valueData.getValue() : 0) ;
						context.put(title.get(colinx).getName(), valueData.getValue()!= null ? valueData.getValue() : 0) ;
						context.put(no, valueData.getValue()!= null ? valueData.getValue() : 0) ;
						context.put(no.toLowerCase(), valueData.getValue()!= null ? valueData.getValue() : 0) ;
					}
					try{
						String express = reportCol.getExpress() ;
						if(express!=null && express.indexOf("$")>=0){
							Map<String , Object> values = new HashMap<String , Object>();
							ValueData tempValueData = reportData.getData().get(rowinx).get(index) ;
							if(tempValueData!=null ){
								values.put("CURRENT", tempValueData.getName()) ;
								express = RivuTools.getTemplet(express, values) ;
							}
						}
						value = AviatorEvaluator.execute(express , context) ;
						if(value!=null&&value.toString().equals("NaN")){
							value = "";
						}
					}catch(Exception ex){
//						reportCol.setExpress("") ;
//						ex.printStackTrace() ;
						value = "";
					}
				}else{
					for(int colinx = start ; colinx < reportData.getData().get(rowinx).size() && (end ==0 || colinx < end) ; colinx++){
						value = mergeValue(value , reportData.getData().get(rowinx).get(colinx) , reportCol.getGrouptype()) ;
					}
				}
				String formatValue = null ;
				String formatStr = reportCol.getFormatstr() ;
				if(formatStr!=null){
					java.text.NumberFormat numberFormat = new DecimalFormat(formatStr);
					if(value!=null && value instanceof Number){
						formatValue = (numberFormat.format(((Number)value).doubleValue())) ;
					}else{
						formatValue = value!=null ? value.toString() : "" ;
					}
				}else{
					formatValue = (String.valueOf(value)) ;
				}

				reportData.getData().get(rowinx).add(index,newColValueData = new ValueData(reportCol.getName(), value, formatValue, "newcol",reportCol.getColtype())) ;
			}else{
				reportData.getData().get(rowinx).add(newColValueData = new ValueData(reportCol.getName(), "", "", "newcol" , reportCol.getColtype())) ;
			}
			if(newColValueData!=null && reportCol.getStyle()!=null){
				newColValueData.setStyle(reportCol.getStyle()) ;
			}
		}
		/**
		 * 以下代码处理 新增列 的 分组聚合
		 */
		if(reportCol.isGroup() && reportCol.getGroupdim()!=null && reportCol.getGroupdim().length()>0){
			List<Level> groupDim = null ;
			for(int i=0 ;reportData.getRow()!=null && reportData.getRow().getFirstTitle()!=null && i< reportData.getRow().getFirstTitle().size() ; i++){
				FirstTitle title  = reportData.getRow().getFirstTitle().get(i) ;
				if(title.getName().equals(reportCol.getGroupdim()) && i<reportData.getRow().getTitle().size()){
					groupDim = reportData.getRow().getTitle().get(i) ;
					break ;
				}
			}
			if(groupDim!=null && groupDim.size()>0){
				for(Level groupRootLevel : groupDim){
					if((groupRootLevel = groupRootLevel.getParent())!=null){
						ValueData valueData = null ;
						valueData = findFirstColGroup(groupRootLevel , reportCol , valueData , index) ;
						//							pricessColGroup(groupRootLevel , reportCol , rowNum) ;
						if(valueData!=null){
							valueData.setCellmergeid(reportCol.getId()!=null ? reportCol.getId():String.valueOf(System.nanoTime())) ;
							valueData.setMerge(false) ;
							valueData.setRow(groupRootLevel);
						}

					}
				}
			}
		}
		/**
		 * 以下代码处理 调整 新增列的位置
		 */
		if(reportCol.getRowindex()>= 0){
			List<Level> titleList = reportData.getCol().getTitle().get(reportData.getCol().getTitle().size()-1) ;
			titleList.add(reportCol.getRowindex() , titleList.remove(titleList.size() - 1 )) ;
			for(int rowinx =0 ; rowinx<reportData.getData().size() ; rowinx++){
				List<ValueData> valueList = reportData.getData().get(rowinx) ;
				valueList.add(reportCol.getRowindex(), valueList.remove(valueList.size()-1)) ;
			}
		}
	}
	
	/**
	 * 处理新增行并调整顺序
	 * @param model
	 * @param reportData
	 * @param colList
	 * @param cube
	 * @throws Exception
	 */
	public static void processNewRow(AnalyzerReportModel model , ReportData reportData  , List<Object> colList, Cube cube)throws Exception{
		List<Object> listCol = new ArrayList<Object>();
		for(Object data : colList){//把混总行的数据抽取出来
			String celltype = BeanUtils.getProperty(data, "type") ;
			if(celltype!=null && celltype.equals("rowcol")){
				listCol.add(data);
			}
		}
		if(listCol.size()>0){
			ReportCol col = null;
			for (int i = 0; i < listCol.size(); i++) {//先处理按照页面汇总行的
				col = (ReportCol)listCol.get(i);
				if(!col.isGroup()){//
					processNewRow(model,reportData,col,cube);
				}
			}
			
			for(int i=0 ; reportData.getRow()!=null&&reportData.getRow().getFirstTitle()!=null && i< reportData.getRow().getFirstTitle().size() ; i++){//处理按照维度汇总的并且按最大级别到最小汇总
				FirstTitle title  = reportData.getRow().getFirstTitle().get(i) ;
				for (int j = 0; j < listCol.size(); j++) {//
					col = (ReportCol)listCol.get(j);
					if(col.isGroup()&&title.getName().equals(col.getGroupdim())){//
						processNewRow(model,reportData,col,cube);
					}
				}
			}
			
		}
	}
	
	/**
	 * 处理重命名
	 * @param model
	 * @param reportData
	 * @param data
	 */
	public static void processRename(AnalyzerReportModel model , ReportData reportData  , List<Object> colList)throws Exception{
		
		for(Object data : colList){
			String celltype = BeanUtils.getProperty(data, "type") ;
			if(celltype!=null && celltype.equals("rename")){
				RenameCol reportCol = (RenameCol) data ;
				
				if(reportData.getRow()!=null && reportData.getRow().getFirstTitle()!=null){
					for(FirstTitle firstTitle : reportData.getRow().getFirstTitle()){
						if(reportCol.getName().equals(firstTitle.getName())){
							firstTitle.setRename(reportCol.getExpress()) ;	//重命名
						}
					}
				}
				if(reportData.getCol()!=null && reportData.getCol().getTitle()!=null){
					for(List<Level> levelList : reportData.getCol().getTitle()){
						for(Level level : levelList){
							if(reportCol.getName().equals(level.getName())){
								level.setRename(reportCol.getExpress()) ;	//重命名
							}
						}
					}
				}
			}
		}
		
	}
	
	
	public static void processReplaceGroupMeasureName(AnalyzerReportModel model , ReportData reportData)throws Exception{
		if(model.getGroupList()==null){
			return;
		}
		for (MeasureGroup group : model.getGroupList()) {
			if(group.getMeasures()==null)continue;
			for (MeasureGroupData measure : group.getMeasures()) {
				if(reportData.getCol()!=null && reportData.getCol().getTitle()!=null){
					for(List<Level> levelList : reportData.getCol().getTitle()){
						for(Level level : levelList){
							if(measure.getOldname().equals(level.getName())){
								level.setName(measure.getNewname());	//替换标题名称
							}
						}
					}
				}
			}
			
		}
	}
	
	
	/**
	 * 处理预警项
	 * @param model模型
	 * @param reportData
	 * @param warningList 
	 */
	public static void processWarning(AnalyzerReportModel model , ReportData reportData){
		if(model.getWarning()!=null && model.getWarning().size()>0){
			List<Warning> warningList = model.getWarning();
			
			for (int i = 0; i < warningList.size(); i++) {
				Warning warn = warningList.get(i);	
				if(reportData.getData()!=null&&reportData.getData().size()>0){
					if("0".equals(warn.getIscomparevalue())){//指标比较
						for (List<ValueData> list_values : reportData.getData()) {
							for (ValueData value : list_values) {
								for (List<ValueData> list_values2 : reportData.getData()) {
									for (ValueData value2 : list_values) {
										if(!(value.getName().equals(warn.getMeasure())&&value2.getName().equals(warn.getComparemeasure())))continue;
										warningCompare(value,value2, warn);
									}
								}
							}
						}
					}else{//值比较
						for (List<ValueData> list_values : reportData.getData()) {
							for (ValueData value : list_values) {
								if(!value.getName().equals(warn.getMeasure()))continue;
								warningCompare(value,null, warn);
							}
						}
					}
				}
			}
		}
	}
	
	/**
	 * 处理千分位
	 * @param model
	 * @param reportData
	 */
	public static void processMicrometer(AnalyzerReportModel model , ReportData reportData){
		if(StringUtils.isBlank(model.getMicrometercolstr())||reportData==null) return;//如果没有的话不进行设置，返回
		
		if(reportData.getCol()!=null && reportData.getCol().getTitle()!=null&&reportData.getCol().getTitle().get(0)!=null){
			List meters = JSON.parseArray(model.getMicrometercolstr(), List.class);
			if(meters==null)return;
			for (Object str : meters) {
				for (List<ValueData> datas :reportData.getData()) {
					for (int i = 0; i < datas.size(); i++) {
						if(datas.get(i).getName().equals(str.toString())){
							datas.get(i).setForamatValue(RivuTools.formatMicrometer(datas.get(i).toString())) ;
						}
					}
				}
			}
		}
		
		
	}
	
	public static void processTitileDescription(ReportData reportData , AnalyzerReportModel model,Cube cube){
		
		
		if(reportData.getRow()!=null && reportData.getRow().getFirstTitle()!=null){
			for(FirstTitle firstTitle : reportData.getRow().getFirstTitle()){
				for (Dimension dim : cube.getDimension()) {
					for (CubeLevel level : dim.getCubeLevel()) {
						if(level.getName().equals(firstTitle.getName())){
							firstTitle.setDescription(level.getDescription());
						}
					}
				}
				
			}
		}
		if(reportData.getCol()!=null && reportData.getCol().getTitle()!=null){
			
			for(List<Level> levellist: reportData.getCol().getTitle()){
					for (Level level : levellist) {
						for (CubeMeasure measure : cube.getMeasure()) {
							if(measure.getName().equals(level.getName())){
								level.setDescription(measure.getDescription());
							}
						}
					}
					
					
			}
		}
	}

	/**
	 * 处理 数据钻取
	 */
	public static ReportData processDrillDown(HttpServletRequest request ,ReportData reportData ,AnalyzerReport analyzerReport, AnalyzerReportModel model)throws Exception{
		
		for(DrillDown drillDown : model.getDrilldown()){
			if(reportData!=null && reportData.getData()!=null && drillDown.isEnable()){
				if(RivuDataContext.DrillDownPosEnum.MEASURE.toString().equals(drillDown.getDrillpos())||RivuDataContext.DrillDownPosEnum.NEWCOL.toString().equals(drillDown.getDrillpos())){
					for (int i = 0; i < reportData.getData().size(); i++) {
						List<ValueData> valueslist = reportData.getData().get(i);
						for (int j = 0; j < valueslist.size(); j++) {
							ValueData valueData = valueslist.get(j);
							if(valueData.getName().equals(drillDown.getDataname())){
								if(RivuDataContext.DrillDownTypeEnum.URL.toString().equals(drillDown.getDrilltype())){
									StringBuffer strb = new StringBuffer().append(drillDown.getParamurl()) ;
									valueData.setUrl(strb.toString()) ;
									valueData.setTarget(drillDown.getParamtarget()) ;
									if(model.isIsexport()){
										valueData.setForamatValue(valueData.getForamatValue());
									}else{
										if(StringUtils.isBlank(valueData.getValueStyle())){
											valueData.setForamatValue(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getForamatValue()).append("</a>").toString()) ;
										}else{
											valueData.setValueStyle(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getValueStyle()).append("</a>").toString()) ;
										}
									}
								}else if(RivuDataContext.DrillDownTypeEnum.DETAIL.toString().equals(drillDown.getDrilltype())){
									StringBuffer strb = new StringBuffer().append("/").append(model.getOrgi()).append("/user/report/reportdrilldown/").append(model.getReportid()).append("/").append(model.getId()).append("/").append(request.getParameter("p")==null?"1":request.getParameter("p")).append("/").append(i).append("/").append(j).append(".html");

									if(model.isIsexport()){
										valueData.setForamatValue(valueData.getForamatValue());
									}else{
										if(StringUtils.isBlank(valueData.getValueStyle())){
											valueData.setForamatValue(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getForamatValue()).append("</a>").toString()) ;
										}else{
											valueData.setValueStyle(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getValueStyle()).append("</a>").toString()) ;
										}
									}
								}else{//钻取到其他报表
									StringBuffer strb = new StringBuffer().append("/").append(model.getOrgi()).append("/user/report/view/").append(drillDown.getReportid()).append(".html");
									strb.append("?drill=true");
									if("paramvalue".equals(drillDown.getParamtype())&&drillDown.getParamvalues()!=null&&drillDown.getParamvalues().size()>0){//处理用户选择的参数
										Iterator it = drillDown.getParamvalues().entrySet().iterator();
										while(it.hasNext()){
											Entry entry = (Entry)it.next();
											if(entry.getValue()==null)continue;
											if(!strb.toString().endsWith("html?")){
												strb.append("&");
											}
											
											if(entry.getValue().toString().startsWith("filter_")){//处理过滤器参数
												ReportFilter filter = null;
										       	for(int k=0 ; k < analyzerReport.getFilters().size() ; k++){
										       		filter = analyzerReport.getFilters().get(k) ;
										       		if(entry.getValue().toString().indexOf(filter.getId())>=0){
										       			if(RivuDataContext.ReportCompareEnum.RANGE.toString().equals(filter.getValuefiltertype())){
										       				strb.append(entry.getKey()+"_start").append("=");
										       				strb.append(filter.getCurstartvalue()!=null?URLEncoder.encode(filter.getCurstartvalue().toString(),"UTF-8"):filter.getCurstartvalue());
										       				strb.append("&");
															strb.append(entry.getKey()+"_end").append("=");
															strb.append(filter.getCurendvalue()!=null?URLEncoder.encode(filter.getCurendvalue().toString(),"UTF-8"):filter.getCurendvalue());
														}else{
															strb.append(entry.getKey()).append("=");
															strb.append(filter.getCurvalue()!=null?URLEncoder.encode(filter.getCurvalue().toString(),"UTF-8"):filter.getCurvalue());
														}
										       			
										       			break;
										       		}
										       		
										       		
										       	}
											}else{//处理维度参数
												strb.append(entry.getKey()).append("=");
												String value = getParentValueByParentName(entry.getValue().toString().replace("dim_", ""), valueData.getRow());
												strb.append(URLEncoder.encode(value.toString(),"UTF-8"));
											}
										
										}
									}
									if(!StringUtils.isBlank(drillDown.getParamvalue())){//处理用户输入的参数
										String value = drillDown.getParamvalue();
										if(value.indexOf("$")>=0){
											Map<String , Object> valueMap = new HashMap<String , Object>();
											valueMap.put("report", analyzerReport);
											valueMap.put("model", model);
											valueMap.put("user", request.getSession(true).getAttribute(RivuDataContext.USER_SESSION_NAME));
											value = RivuTools.getTemplet(drillDown.getParamvalue(), valueMap) ;
										}
										
										if(strb.toString().endsWith("html")){
											strb.append("?");
										}else{
											strb.append("&");
										}
										strb.append(value);
									}
									if(model.isIsexport()){
										valueData.setForamatValue(valueData.getForamatValue());
									}else{
										String reg = "^[-+]?(([0-9]+)([.]([0-9]+))?|([.]([0-9]+))?)$";
										if(drillDown.getGotomaxvalue()!=null&&!StringUtils.isBlank(drillDown.getGotomaxvalue())&&drillDown.getGotomaxvalue().matches(reg)&&valueData.getForamatValue().matches(reg)){
											if(new BigDecimal(drillDown.getGotomaxvalue()).compareTo(new BigDecimal(valueData.getForamatValue()))>=0){
												if(StringUtils.isBlank(valueData.getValueStyle())){
													valueData.setForamatValue(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getForamatValue()).append("</a>").toString()) ;
												}else{
													valueData.setValueStyle(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getValueStyle()).append("</a>").toString()) ;
												}
											}
											
										}else{
											if(StringUtils.isBlank(valueData.getValueStyle())){
												valueData.setForamatValue(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getForamatValue()).append("</a>").toString()) ;
											}else{
												valueData.setValueStyle(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='m_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(valueData.getValueStyle()).append("</a>").toString()) ;
											}
										}
										
										
										
									}
									
								}
							}
						}
					}
					
				}else if(RivuDataContext.DrillDownPosEnum.DIM.toString().equals(drillDown.getDrillpos())){
					if(reportData.getRow()!=null && reportData.getRow().getFirstTitle()!=null){
						for(int i=0 ; i<reportData.getRow().getFirstTitle().size() ; i++){
							FirstTitle firstTitle = reportData.getRow().getFirstTitle().get(i) ;
							if(drillDown.getDataname().equals(firstTitle.getName()) && reportData.getRow().getTitle()!=null && i < reportData.getRow().getTitle().size()){
								List<Level> titleList = reportData.getRow().getTitle().get(i) ;
								for(Level level : titleList){
									Map<String,Object> values = new HashMap<String,Object>();
									Level temp = level ;
									while(temp!=null && temp.getParent()!=null && !temp.getParent().getName().equals("root")){
										values.put(temp.getParent().getDimname(), temp.getParent().getName());
										temp = temp.getParent();
									}
									if(RivuDataContext.DrillDownTypeEnum.URL.toString().equals(drillDown.getDrilltype())){
										StringBuffer strb = new StringBuffer();
										try {
											level.setUrl(RivuTools.getTemplet(drillDown.getParamurl(), values)) ;
											strb.append(level.getUrl()) ;
										} catch (IOException e) {
											// TODO Auto-generated catch block
											e.printStackTrace();
										} catch (TemplateException e) {
											// TODO Auto-generated catch block
											e.printStackTrace();
										}
										level.setTarget(drillDown.getParamtarget()) ;
										if(model.isIsexport()){
											level.setFormatName((level.getRename()!=null ? level.getRename() : level.getName()));
										}else{
											level.setFormatName(strb.insert( 0 , "<a href='").append("' ").append(drillDown.getParamtarget()!=null && drillDown.getParamtarget().equals("_blank")?"target='_blank'":"").append(" class='dim_").append(RivuTools.md5(drillDown.getDataname())).append("'>").append(level.getRename()!=null ? level.getRename() : level.getName()).append("</a>").toString()) ;
										}
									}else if(RivuDataContext.DrillDownTypeEnum.DETAIL.toString().equals(drillDown.getDrilltype())){
										
									}
								}
							}
						}
					}
				}
			}
		}
		return reportData ;
	}
	
	private static String getParentValueByParentName(String parentName,Level level){
		String result = "";
		
		if(level!=null&&"R3_TOTAL".equals(level.getNameValue()))
			level = level.getParent();
		
		if(level==null) return result;
		
		if(parentName.equals(level.getDimname())){
			return level.getName();
		}else{
			result = getParentValueByParentName(parentName, level.getParent());
		}
		
		return result;
	}
	
	/**
	 * 计算值
	 * @param mergeValue
	 * @param mergeData
	 * @param mergeType
	 * @return
	 */
	private static Object mergeValue(Object mergeValue , ValueData mergeData , String mergeType){
		if(mergeValue!=null){
			if(("sum".equals(mergeType) || "avg".equals(mergeType) || "count".equals(mergeType) || "distinct-count".equals(mergeType) || "avgexp".equals(mergeType)) && mergeData.getValue()!=null){
				if(mergeData.getValue() instanceof Byte){
					mergeValue = (((Number) mergeValue).doubleValue()+((Byte)mergeData.getValue()).byteValue()) ;
				}else if(mergeData.getValue() instanceof Integer){
					mergeValue = (((Number)mergeValue).doubleValue()+((Integer)mergeData.getValue()).intValue()) ;
				}else if(mergeData.getValue() instanceof Float){
					mergeValue = (((Number)mergeValue).doubleValue()+((Float)mergeData.getValue()).floatValue()) ;
				}else if(mergeData.getValue() instanceof Double){
					mergeValue = (((Number)mergeValue).doubleValue()+((Double)mergeData.getValue()).doubleValue()) ;
				}else if(mergeData.getValue() instanceof Number){
					mergeValue = (((Number)mergeValue).doubleValue()+((Number)mergeData.getValue()).doubleValue()) ;
				}
			}
			if("max".equals(mergeType)){
				if(mergeData.getValue()!=null){
					if(((Number)mergeValue).doubleValue() < ((Number)mergeData.getValue()).doubleValue()){
						mergeValue = (mergeData.getValue()) ;
					}
				}
			}
			if("min".equals(mergeType)){
				if(mergeData.getValue()!=null){
					if(((Number)mergeValue).doubleValue() > ((Number)mergeData.getValue()).doubleValue()){
						mergeValue = (mergeData.getValue()) ;
					}
				}
			}
		}else if(mergeData.getValue() instanceof Number){
			mergeValue = (mergeData.getValue()) ;
		}
		return mergeValue ;
	}
	
	private static void aggValueData(String mergeType , int avgNum , Object mergeValue , ValueData valueData , String format){
		if(("avg".equals(mergeType) || "avgexp".equals(mergeType)) && avgNum>0){
			mergeValue = (((Number)(mergeValue)).doubleValue() / avgNum);
		}
		if(mergeValue!=null){
			String formatStr = format!=null ? format : valueData.getFormatStr() ;
			if(formatStr!=null){
				java.text.NumberFormat numberFormat = new DecimalFormat(formatStr);
				if(mergeValue!=null && mergeValue instanceof Number){
					valueData.setForamatValue(numberFormat.format(((Number)mergeValue).doubleValue())) ;
				}
			}else{
				valueData.setForamatValue(String.valueOf(mergeValue)) ;
			}
			valueData.setValue(mergeValue) ;
		}
	}
	
	private static ValueData findFirstColGroup(Level rootLevel , ReportCol group , ValueData valueData , int index){
		Level tempLevel = rootLevel ;
		while(tempLevel.getChilderen()!=null){
			if(tempLevel.getChilderen().size()>0){
				tempLevel = tempLevel.getChilderen().get(0) ;
			}
		}
		if(tempLevel!=null && tempLevel.getValueData()!=null && tempLevel.getValueData().size()>0){
			valueData = tempLevel.getValueData().get(index) ;
//			Object mergeValue = null ;
//			for(Level child : tempChild.getParent().getChilderen()){
//				ValueData mrgetValue = child.getValueData().get(child.getValueData().size()-1) ;
//				mrgetValue.setMerge(true) ;
//				mergeValue = mergeValue(mergeValue,mrgetValue , group.getGrouptype()) ;
//			}
			processColGroup(rootLevel , group , valueData , index);
			valueData.setValue(valueData.getTempValue()) ;
		}
		if(valueData!=null){
			valueData.setRowspan(rootLevel.getRowspan()) ;
		}
		aggValueData(group.getGrouptype() , rootLevel.getRowspan() , valueData.getTempValue() , valueData , group.getFormatstr()) ;
 		return valueData ;
	}
	
	
	/**
	 * 处理 新增行
	 * @param model
	 * @param reportData
	 * @param data
	 */
	private static void processNewRow(AnalyzerReportModel model , ReportData reportData  , ReportCol data , Cube cube){
		ReportCol reportCol = (ReportCol) data ;
		Level totalRow = null ;
		if(reportCol.isGroup() && reportCol.getGroupdim()!=null && reportCol.getGroupdim().length()>0){//分组汇总
			List<Level> groupDim = null ;
			int colnum = 0;
			for(int i=0 ; reportData.getRow().getFirstTitle()!=null && i< reportData.getRow().getFirstTitle().size() ; i++){
				FirstTitle title  = reportData.getRow().getFirstTitle().get(i) ;
				if(title.getName().equals(reportCol.getGroupdim()) && i<reportData.getRow().getTitle().size()){
					groupDim = reportData.getRow().getTitle().get(i) ;
					colnum = i;
					break ;
				}
			}
			if(groupDim!=null && groupDim.size()>0){
				for (int i = 0; i < groupDim.size(); i++) {
					Level groupRootLevel = groupDim.get(i);
				
					if((groupRootLevel = groupRootLevel.getParent())!=null){
						if(groupRootLevel.getChilderen()!=null&&groupRootLevel.getChilderen().size()>1){
							
							groupDim.add(i+1,new Level(reportCol.getName() , reportCol.getId(), "newrow", 1 , reportData.getRow().getTitle().size()-colnum , null , false , false)) ;//添加汇总行标题
							Level level = addGroupSumRow(null,groupRootLevel,reportData,reportCol,sumRowByLevels(groupDim,i));
							
							List<ValueData> newRowList = new ArrayList<ValueData>();
							for(int colindex =0 ; reportData.getData()!=null && reportData.getData().size()>0 && colindex < reportData.getData().get(0).size() ; colindex++){
								CubeMeasure measure = null ;
								Object value = null ;
								ValueData newColValueData = null ;
								String formatStr = reportCol.getFormatstr() ;
								int count = 0;
								for(int rowindex = sumRowByLevels(groupDim,i-1) ; rowindex < sumRowByLevels(groupDim,i) ; rowindex++){
									ValueData valueData = reportData.getData().get(rowindex).get(colindex) ;
									
									if(measure == null){
										measure = getCubeMeasure(cube , valueData.getName()) ;
									}
									
									if(valueData.getFormatStr()!=null && valueData.getFormatStr().length()>0){
										formatStr = valueData.getFormatStr() ;
									}
									if(!valueData.isMerge()){
										
										value = mergeValue(value , valueData , measure!=null ? measure.getAggregator() : "sum") ;
									}
									count++;
								}
								if("avg".equals(measure!=null ? measure.getAggregator() : "sum") && reportData.getData().size()>0 && value instanceof Number){
									value = ((Number)value).doubleValue() / count ;
								}
								String formatValue = null ;
								if(formatStr!=null){
									java.text.NumberFormat numberFormat = new DecimalFormat(formatStr);
									if(value!=null && value instanceof Number){
										formatValue = (numberFormat.format(((Number)value).doubleValue())) ;
									}else{
										formatValue = value!=null ? value.toString() : "" ;
									}
								}else{
									formatValue = (String.valueOf(value)) ;
								}

								newRowList.add(newColValueData = new ValueData(reportCol.getId(), value, formatValue, "newrow",reportCol.getColtype())) ;
							}
							parentAddRowspan(groupRootLevel,reportData,sumRowByLevels(groupDim, i));
							level.setValueData(newRowList) ;
							reportData.getData().add(sumRowByLevels(groupDim,i),newRowList) ;
						
						}
					}
				}
			}
		}else{//当前页汇总
			
			
			List<ValueData> newRowList = new ArrayList<ValueData>();
			if(reportData.getRow()!=null && reportData.getRow().getTitle()!=null && reportData.getRow().getTitle().size()>0){
				reportData.getRow().getTitle().get(0).add(totalRow = new Level(reportCol.getName() , reportCol.getId(), "newrow", 1 , reportData.getRow().getTitle().size() , null , false , false)) ;
				totalRow.setValueData(newRowList) ;
			}
			
			for(int colindex =0 ; reportData.getData()!=null && reportData.getData().size()>0 && colindex < reportData.getData().get(0).size() ; colindex++){
				ValueData newColValueData = null ;
				if(reportCol.getExpress()!=null && reportCol.getExpress().length()>0){
					String formatStr = reportCol.getFormatstr() ;
					Object value = null ;
					if(!reportCol.getExpress().equalsIgnoreCase("ALL")){
						Map<String , Object> context = new HashMap<String , Object>();
						for(int rowindex = 0 ; rowindex < reportData.getData().size() ; rowindex++){
							ValueData valueData = reportData.getData().get(rowindex).get(colindex) ;
							String no = RivuTools.getInx2Char(rowindex) ;
							/**
							 * JEXL 2 不支持中文标签名称
							 */
							//										context.set(valueData.getName(), valueData.getValue()!= null ? valueData.getValue() : 0) ;
							context.put(valueData.getName(), valueData.getValue()!= null ? valueData.getValue() : 0) ;
							context.put(no, valueData.getValue()!= null ? valueData.getValue() : 0) ;
							context.put(no.toLowerCase(), valueData.getValue()!= null ? valueData.getValue() : 0) ;
						}
						try{
							value = AviatorEvaluator.execute(reportCol.getExpress() ,context) ;
						}catch(Exception ex){
							ex.printStackTrace() ;
							value = ex.getMessage();
						}
					}else{
						CubeMeasure measure = null ;
						for(int rowindex = 0 ; rowindex < reportData.getData().size() ; rowindex++){
							ValueData valueData = reportData.getData().get(rowindex).get(colindex) ;
							
							if(measure == null){
								measure = getCubeMeasure(cube , valueData.getName()) ;
							}
							
							if(valueData.getFormatStr()!=null && valueData.getFormatStr().length()>0){
								formatStr = valueData.getFormatStr() ;
							}
							if(!valueData.isMerge()){
								
								value = mergeValue(value , valueData , measure!=null ? measure.getAggregator() : "sum") ;
							}
						}
						if("avg".equals(measure!=null ? measure.getAggregator() : "sum") && reportData.getData().size()>0 && value instanceof Number){
							value = ((Number)value).doubleValue() / reportData.getData().size() ;
						}
					}
					String formatValue = null ;
					if(formatStr!=null){
						java.text.NumberFormat numberFormat = new DecimalFormat(formatStr);
						if(value!=null && value instanceof Number){
							formatValue = (numberFormat.format(((Number)value).doubleValue())) ;
						}else{
							formatValue = value!=null ? value.toString() : "" ;
						}
					}else{
						formatValue = (String.valueOf(value)) ;
					}

					newRowList.add(newColValueData = new ValueData(reportCol.getId(), value, formatValue, "newrow",reportCol.getColtype())) ;
				}else{
					newRowList.add(newColValueData = new ValueData(reportCol.getId(), "", "", "newrow" , reportCol.getColtype())) ;
				}
				if(newColValueData!=null && reportCol.getStyle()!=null){
					newColValueData.setStyle(reportCol.getStyle()) ;
				}
			}
			
			/**
			 * 添加汇总行
			 */
			reportData.getData().add(newRowList) ;
		}
		
		
	}
	
	private static void parentAddRowspan(Level parent,ReportData reportData,int index){
		List<Level> groupDim = null ;
		
		if(parent.getParent()!=null){
			String colname = parent.getParent().getDimname();
			for(int i=0 ; reportData.getRow().getFirstTitle()!=null && i< reportData.getRow().getFirstTitle().size() ; i++){
				FirstTitle title  = reportData.getRow().getFirstTitle().get(i) ;
				if(title.getName().equals(colname) && i<reportData.getRow().getTitle().size()){
					groupDim = reportData.getRow().getTitle().get(i) ;
					Level level = groupDim.get(sumIndexByLevels(groupDim,index));
					level.setRowspan(level.getRowspan()+1);
					parentAddRowspan(parent.getParent(),reportData,index);
					break ;
				}
			}
		}
		parent.setRowspan(parent.getRowspan()+1);
		
	}
	
	
	
	
	/**
	 * 根据位置计算行数
	 * @param groupDim
	 * @param rownum
	 * @return
	 */
	private static int sumRowByLevels(List<Level> groupDim,int index){
		int row = 0;
		for (int i = 0; i < groupDim.size(); i++) {
			if(i<=index){
				row=row+Integer.valueOf(groupDim.get(i).getRowspan());
			}else{
				break;
			}
			
		}
		
		return row;
	}
	/**
	 * 根据行数计算位置
	 * @param groupDim
	 * @param rownum
	 * @return
	 */
	private static int sumIndexByLevels(List<Level> groupDim,int rownum){
		int index = 0;
		int count = 0;
		for (int i = 0; i < groupDim.size(); i++) {
			
			count = count+Integer.valueOf(groupDim.get(i).getRowspan());
			if(count>=rownum){
				index=i;
				break;
			}
			
		}
		
		return index;
	}
	
	
	
	private static Level addGroupSumRow(Level level,Level rootlevel,ReportData reportData,ReportCol reportCol,int rolnum){

		List<Level> groupDim = null ;
		
		if(rootlevel.getChilderen()!=null&&rootlevel.getChilderen().size()>0){
			String colname = rootlevel.getChilderen().get(0).getDimname();
			for(int i=0 ; reportData.getRow().getFirstTitle()!=null && i< reportData.getRow().getFirstTitle().size() ; i++){
				FirstTitle title  = reportData.getRow().getFirstTitle().get(i) ;
				if(title.getName().equals(colname) && i<reportData.getRow().getTitle().size()){
					groupDim = reportData.getRow().getTitle().get(i) ;
					groupDim.add(sumIndexByLevels(groupDim,rolnum)+1,level = new Level(reportCol.getName() , reportCol.getId(), "newrow_extend_sum", 1 , 1 , null , false , false)) ;//添加汇总行标题
					addGroupSumRow(level,groupDim.get(sumIndexByLevels(groupDim,rolnum)).getParent(),reportData,reportCol,rolnum);
					
					break ;
				}
			}
			
		}else{
			level = rootlevel;
		}
		return level;
	}
	
	
	
	private static void warningCompare(ValueData value,ValueData compareValue,Warning warn){
		BigDecimal datavalue = new BigDecimal(StringUtils.isBlank(value.getValue().toString())?"0":value.getValue().toString());
		BigDecimal comparevalue = null;
		if(compareValue==null){
			comparevalue = new BigDecimal(warn.getComparevalue());
		}else{
			comparevalue = new BigDecimal(StringUtils.isBlank(compareValue.getValue().toString())?"0":compareValue.getValue().toString());
		}

		String condition = warn.getCondition();
		boolean flag = false;
		if("=".equals(condition)&&datavalue.compareTo(comparevalue)==0){
			flag=true;
		}else if("!=".equals(condition)&&datavalue.compareTo(comparevalue)!=0){
			flag=true;
		}else if("<".equals(condition)&&datavalue.compareTo(comparevalue)<0){
			flag=true;
		}else if("<=".equals(condition)&&(datavalue.compareTo(comparevalue)==0||datavalue.compareTo(comparevalue)<0)){
			flag=true;
		}else if(">".equals(condition)&&datavalue.compareTo(comparevalue)>0){
			flag=true;
		}else if(">=".equals(condition)&&(datavalue.compareTo(comparevalue)==0||datavalue.compareTo(comparevalue)>0)){
			flag=true;
		}
		if(flag){
			value.setValueStyle(null);
			setValueStyle(value, warn);
		}
	}
	
	/**
	 * 拼接每个value值得样式
	 * @param value
	 * @param warn
	 */
	private static void setValueStyle(ValueData value,Warning warn){
		String convalue = warn.getConvalue();
		String valuestyle = value.getValueStyle();
		if(valuestyle==null){
			valuestyle = "<pre style=''>"+value.getForamatValue()+"</pre>";
		}
		String stylestr = valuestyle.substring(valuestyle.indexOf("'")+1,valuestyle.indexOf("'", valuestyle.indexOf("'")+1));
		if("color".equals(convalue)){
			if(stylestr.indexOf("color:")>0){
				stylestr = stylestr.substring(0,stylestr.indexOf("color:")+6)+warn.getStylevalue()+stylestr.substring(stylestr.indexOf(";",stylestr.indexOf("color:")),stylestr.length());
			}else{
				stylestr+="color:"+warn.getStylevalue()+";";
			}
				
		}else if("class".equals(convalue)){
			if("left".equals(warn.getAlign())){
				if(valuestyle.indexOf("<img")>0){
					valuestyle = valuestyle.substring(0,valuestyle.indexOf("<img")+4)+" src='"+warn.getStylevalue()+"' align='"+"left' width='20' height='20'"+valuestyle.substring(valuestyle.indexOf("/>",valuestyle.indexOf("<img")),valuestyle.length());
				}else{
					valuestyle = valuestyle.substring(0,valuestyle.indexOf(">")+1)+"<img src='"+warn.getStylevalue()+"' align='left' width='20' height='20'/>"+value.getForamatValue()+valuestyle.substring(valuestyle.lastIndexOf("<"),valuestyle.length());
				}
				
			}else if("right".equals(warn.getAlign())){
				if(valuestyle.indexOf("<img")>0){
					valuestyle = valuestyle.substring(0,valuestyle.indexOf("<img")+4)+" src='"+warn.getStylevalue()+"' align='"+"right' width='20' height='20'"+valuestyle.substring(valuestyle.indexOf("/>",valuestyle.indexOf("<img")),valuestyle.length());
				}else{
					valuestyle = valuestyle.substring(0,valuestyle.indexOf(">")+1)+"<img src='"+warn.getStylevalue()+"' align='right' width='20' height='20'/>"+value.getForamatValue()+valuestyle.substring(valuestyle.lastIndexOf("<"),valuestyle.length());
				}
				
			}else{
				if(valuestyle.indexOf("<img")>0){
					valuestyle = valuestyle.substring(0,valuestyle.indexOf("<img")+4)+" src='"+warn.getStylevalue()+"' width='20' height='20'/>"+valuestyle.substring(valuestyle.lastIndexOf("<"),valuestyle.length());
				}else{
					valuestyle = valuestyle.substring(0,valuestyle.indexOf(">")+1)+"<img src='"+warn.getStylevalue()+"' width='20' height='20'/>"+valuestyle.substring(valuestyle.lastIndexOf("<"),valuestyle.length());
				}
			}
			
			
		}else if("backgroundcolor".equals(convalue)){
			if(stylestr.indexOf("background:")>0){
				stylestr = stylestr.substring(0,stylestr.indexOf("background:")+11)+warn.getStylevalue()+stylestr.substring(stylestr.indexOf(";",stylestr.indexOf("background:")),stylestr.length());
			}else{
				stylestr+="background:"+warn.getStylevalue()+";";
			}
		}else if("fontstyle".equals(convalue)){
			if(stylestr.indexOf("font-weight:")>0){
				stylestr = stylestr.substring(0,stylestr.indexOf("font-weight:")+12)+warn.getStylevalue()+stylestr.substring(stylestr.indexOf(";",stylestr.indexOf("font-weight:")),stylestr.length());
			}else{
				stylestr+="font-weight:"+warn.getStylevalue()+";";
			}
			
		}else if("text".equals(convalue)){
			valuestyle = valuestyle.substring(0,valuestyle.indexOf(">")+1)+warn.getStylevalue()+valuestyle.substring(valuestyle.lastIndexOf("<"),valuestyle.length());
		}
		valuestyle = valuestyle.substring(0,valuestyle.indexOf("'")+1)+stylestr+valuestyle.substring(valuestyle.indexOf("'",valuestyle.indexOf("'")+1),valuestyle.length());
		value.setValueStyle(valuestyle);
	}
	
	/**
	 * 获取 汇总行 的 指标聚合方式
	 * @param cube
	 * @param name
	 * @return
	 */
	private static CubeMeasure getCubeMeasure(Cube cube , String name){
		CubeMeasure cubeMeasure = null ;
		if(cube!=null && cube.getMeasure()!=null){
			for(CubeMeasure measure : cube.getMeasure()){
				if(measure.getName().equals(name)){
					cubeMeasure = measure ;
					break ;
				}
			}
		}
		return cubeMeasure ;
	}
	
	private static void processColGroup(Level root , ReportCol group , ValueData firstData ,  int index){
		if(root.getChilderen()==null){
			if(root.getValueData()!=null && root.getValueData().size()>0){
				ValueData valueData = root.getValueData().get(index) ;
				valueData.setMerge(true) ;
				Object mergeValue = mergeValue(firstData.getTempValue(), valueData, group.getGrouptype()) ;
				firstData.setTempValue(mergeValue) ;
				valueData.setMergevalue(firstData) ;
			}
		}else{
			for(Level child : root.getChilderen()){
				processColGroup(child , group , firstData , index) ;
			}
		}
	}
	
}
